FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 1 1 ;^Z80^ 2 ; modem control information 3 ; Coleco 300 baud direct connect modem 4 ; 4/5/84 5 ; 6 ; Data port = 05EH 7 ; Control port = 05FH 8 ; 9 ; Useful equates 10 005E DATAP EQU 05EH 11 005F CTRLP EQU 05FH 12 ; 13 ; Mode instruction values 14 0080 NULL EQU 080H 15 ; 16 ; To generate mode byte, select one from column A 17 ; and one from column B. See your INTEL dealer for optional 18 ; accessories. Add these all together, and spit 'em out. 19 ; Chef's suggestion: DEFAULT EQU STPB1+BITS7+PEN+EP 20 ; [7 bits, 1 stop bit, even parity] 21 ; 22 ; column A 23 0040 STPB1 EQU 040H ; 1 stop bit 24 0080 STPB15 EQU 080H ; 1 1/2 stop bits 25 00C0 STPB2 EQU 0C0H ; 2 stop bits 26 ; column B 27 0000 BITS5 EQU 000H ; 5 bits/char 28 0004 BITS6 EQU 004H ; 6 bits/char 29 0008 BITS7 EQU 008H ; 7 bits/char 30 000C BITS8 EQU 00CH ; 8 bits/char 31 ; optional accessories 32 0020 EP EQU 020H ; 1=even parity, 0=odd 33 0010 PEN EQU 010H ; 1=enable parity, 0=disable 34 ; required options 35 ; ---> The only one applicable here is 300 baud!!! <--- 36 0003 X64 EQU 003H ; 64x clock rate [300 baud] 37 ; 38 ; the assumed default value 39 00CC DEFAULT EQU STPB2+BITS8 ; 8 bits, 2 stops, no parity 40 ; Command instruction values 41 ; 42 ; Select desired functions, then add to get command byte 43 ; 44 0080 EHM EQU 080H ; 1=enter hunt mode [no effect on async op] 45 ; [same as NULL] 46 0040 IR EQU 040H ; 1=internal reset 47 0020 RTS EQU 020H ; 1=set RTS to 0, enable transmitter 48 0010 ER EQU 010H ; 1=reset error conditions 49 0008 SBRK EQU 008H ; 1=send break [TXD goes "low"] 50 0004 RXE EQU 004H ; 1=receive enable 51 0001 TXE EQU 001H ; 1=transmit enable 52 0002 DTR EQU 002H ; set DTR to 0, seize phone line 53 ; 54 ; Note this important stuff | 55 ; V 56 ; 1: If DTR ever gets set to 0, [SZ or preset goes low] then FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 2 57 ; modem goes to originate mode. 58 ; 2: Once line is seized, DTR is set to 1, ^SZ is low, so 59 ; 7474 has preset=H, data=L,.html clear=H. In this condition, 60 ; toggling clock [RTS or ^TXE] will change to answer mode 61 ; 62 ; So what? 63 ; 64 ; With phone hung up, modem is in originate mode. To seize line, 65 ; set DTR and RTS to 1 [this drops ^SZ]. This grabs phone line 66 ; and enables carrier. 67 ; To switch to answer mode, set RTS to 0 then back to 1. 68 ; 69 ; STATUS BITS 70 ; 71 0000 TXRDY EQU 0 ; indicates transmitter empty 72 0001 RXRDY EQU 1 ; indicates valid character ready 73 0002 TXMT EQU 2 ; indicates buffer empty 74 0003 P_ERR EQU 3 ; set when parity error detected 75 0004 OE EQU 4 ; set on overrun error 76 0005 FE EQU 5 ; set on framing error 77 0006 BD EQU 6 ; set when break detected 78 0007 DSR EQU 7 ; indicated carrier detect 79 0007 CD EQU DSR 80 ; 81 ; data areas 82 0000' 80 C_DATA DEFB NULL ; current 8251 command 83 ; 84 ; global subroutine names 85 ; 86 GLOBAL DELAY,DIAL,SEIZE,ANSMOD 87 GLOBAL HANGUP,CD_STAT,U_STAT 88 GLOBAL CHR_IN,CHR_OUT,M_INIT 89 GLOBAL SET_UART 90 ; 91 ;*************************************************************************** 92 ; SUBROUTINES 93 ;*************************************************************************** 94 ; 95 ; Wait 10 msec 96 0001' DELAY: 97 0001' F5 PUSH AF ; [3 uSEC] 98 0002' C5 PUSH BC ; [3] 99 0003' D5 PUSH DE ; [3] 100 0004' E5 PUSH HL ; [3] 101 0005' 21 0000 LD HL,0 ; [2.5] 102 0008' 11 0000 LD DE,0 ; [2.5] 103 000B' 01 3606 LD BC,1590 104 ; with all the pushes and pops, we've used about 32 uSEC. 105 ; we need a total of 2,000 LDIRs less 7 106 ; BUT this is off a bit, so we have to go about 18% faster 107 000E' ED B0 LDIR 108 0010' E1 POP HL ; [3] 109 0011' D1 POP DE ; [3] 110 0012' C1 POP BC ; [3] 111 0013' F1 POP AF ; [3] 112 0014' C9 RET 113 ; FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 3 114 ; ************************************* 115 ; DIAL DIGIT 116 ; ENTRY: A=ASCII DIGIT 0-9 117 ; EXIT: NONE 118 0015' DIAL: 119 0015' F5 PUSH AF 120 0016' C5 PUSH BC 121 0017' D5 PUSH DE 122 0018' E5 PUSH HL 123 ;thaT 124 0019' FE 50 CP 'P' 125 001B' 28 36 JR Z,PAUSE 126 001D' FE 70 CP 'p' 127 001F' 28 32 JR Z,PAUSE 128 0021' FE 2C CP ',' ;Comma=pause 129 0023' 28 2E JR Z,PAUSE 130 0025' FE 3A CP '9'+1 131 0027' 30 31 JR NC,BAD_DGT ;if character >= ':' then we lose 132 0029' FE 30 CP '0' 133 002B' 38 2D JR C,BAD_DGT ;if char < '0' then we lose 134 002D' 20 02 JR NZ,CHAR_OK 135 ; an ASCII 0 means 10 pulses, so start with '9'+1 136 002F' 3E 3A LD A,'9'+1 137 0031' CHAR_OK: 138 0031' D6 30 SUB '0' 139 0033' 47 LD B,A ;number of pulses is now in B 140 ; 141 0034' PLSE_LP: 142 ; All dialing is in originate mode. We assume that the line was 143 ; already seized. 144 ; 145 ; unseize line for 18/29 of the 100 ms pulse time [60 ms] 146 0034' 3E 25 LD A,RXE+TXE+RTS 147 0036' D3 5F OUT (CTRLP),A ;PICK UP 148 0038' C5 PUSH BC 149 0039' 06 06 LD B,6 150 003B' PLP1: 151 003B' CD 0100' CALL DELAY 152 003E' 10 FB DJNZ PLP1 153 0040' C1 POP BC 154 ; seize line for 11/29 of the 100 ms pulse time [40 ms] 155 0041' 3E 27 LD A,RXE+TXE+RTS+DTR 156 0043' D3 5F OUT (CTRLP),A ;PICK UP 157 0045' C5 PUSH BC 158 0046' 06 04 LD B,4 159 0048' PLP2: 160 0048' CD 0100' CALL DELAY 161 004B' 10 FB DJNZ PLP2 162 004D' C1 POP BC 163 ; 164 ; next pulse 165 004E' 10 E4 DJNZ PLSE_LP 166 167 0050' 32 0000' LD (C_DATA),A ;SAVE LAST VALUE 168 ; 169 ; delay between digits 170 0053' PAUSE: FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 4 171 0053' 06 50 LD B,80 ;800 ms 172 0055' PLP3: 173 0055' CD 0100' CALL DELAY 174 0058' 10 FB DJNZ PLP3 175 005A' BAD_DGT: 176 005A' E1 POP HL 177 005B' D1 POP DE 178 005C' C1 POP BC 179 005D' F1 POP AF 180 005E' C9 RET 181 182 ; *************************** 183 ; SEIZE LINE 184 ; ENTRY: A=0 FOR ORIGINATE MODE 185 ; A-0FFH FOR ANSWER MODE 186 ; EXIT: CARRIER IS ENABLED 187 ; REGS A & C GET TRASHED 188 005F' SEIZE: 189 005F' 4F LD C,A ; SAVE 190 0060' CD 7900' CALL HANGUP 191 0063' 3E 27 LD A,RXE+TXE+RTS+DTR 192 0065' 32 0000' LD (C_DATA),A ; SAVE LAST COMMAND 193 0068' D3 5F OUT (CTRLP),A ; PICK UP 194 006A' 79 LD A,C 195 006B' B7 OR A 196 006C' C8 RET Z ; ALL DONE 197 ; ***************** 198 ; ANSWER MODE 199 ; SWITCHES MODEM DIRECTLY TO ANSWER MODE 200 ; Assumes modem off-hook 201 ; EXIT: REG A TRASHED 202 006D' ANSMOD: 203 ; ONE FULL PULSE OF RTS LINE 204 006D' 3E 07 LD A,RXE+TXE+DTR 205 006F' D3 5F OUT (CTRLP),A 206 0071' 3E 27 LD A,RXE+TXE+RTS+DTR 207 0073' 32 0000' LD (C_DATA),A ; SAVE LAST COMMAND 208 0076' D3 5F OUT (CTRLP),A 209 0078' C9 RET 210 ; ********************** 211 ; HANGUP 212 ; HANGS UP PHONE. TRASHES REG A 213 ; 214 0079' HANGUP: 215 0079' 3E 25 LD A,RXE+TXE+RTS 216 007B' 32 0000' LD (C_DATA),A ; SAVE LAST COMMAND 217 007E' D3 5F OUT (CTRLP),A ; HANG UP PHONE AND SWITCH TO ORIGINATE MODE 218 0080' C9 RET 219 ; ********************** 220 ; CARRIER_STATUS 221 ; READS STATUS FROM UART AND MODEM CHIP 222 ; ENTRY: 223 ; EXIT: NZ=CARRIER DETECT 224 ; Z=NO CARRIER 225 0081' CD_STAT: 226 0081' DB 5F IN A,(CTRLP) 227 0083' CB 7F BIT DSR,A FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 5 228 0085' C9 RET 229 ; ********************** 230 ; UART_STATUS 231 ; CHECKS UART FOR ERRORS AND/OR DATA 232 ; ENTRY: 233 ; EXIT: NC=NO ERRORS 234 ; C=DATA ERROR 235 ; NZ=CHARACTER PRESENT 236 ; Z=NO CHARACTER 237 0086' U_STAT: 238 0086' DB 5F IN A,(CTRLP) 239 0088' B7 OR A 240 0089' 18 01 JR URT_CMN 241 008B' URT_ERR: 242 008B' 37 SCF 243 008C' URT_CMN: 244 008C' CB 4F BIT RXRDY,A 245 008E' C9 RET 246 ; ************************ 247 ; CHARACTER_IN 248 ; ENTRY: 249 ; EXIT: A=CHARACTER FROM MODEM 250 ; NC=NO ERROR 251 ; C=DATA ERROR 252 253 008F' CHR_IN: 254 008F' CD 8600' CALL U_STAT 255 0092' 28 FB JR Z,CHR_IN ;WAIT FOR CHARACTER 256 0094' DB 5E IN A,(DATAP) 257 0096' B7 OR A 258 0097' C9 RET 259 0098' CHR_ERR: 260 0098' 3A 0000' LD A,(C_DATA) 261 009B' F6 10 OR ER ;clear for errors 262 009D' D3 5F OUT (CTRLP),A 263 009F' EE 10 XOR ER ;disable error reset 264 00A1' D3 5F OUT (CTRLP),A 265 00A3' 3E 00 LD A,0 266 00A5' C9 RET 267 ; ********************* 268 ; CHARACTER_OUT 269 ; ENTRY: A=CHARACTER TO TRANSMIT 270 ; EXIT: NONE 271 00A6' CHR_OUT: 272 00A6' F5 PUSH AF 273 ; WAIT UNTIL TRANSMITTER CLEAR 274 00A7' CHR_L1: 275 00A7' DB 5F IN A,(CTRLP) 276 00A9' CB 57 BIT TXMT,A 277 00AB' 28 FA JR Z,CHR_L1 278 ; DUMP THE SUCKER OUT 279 00AD' F1 POP AF 280 00AE' D3 5E OUT (DATAP),A 281 00B0' C9 RET 282 ; ************************* 283 ; MODEM_INIT 284 ; PRESETS MODEM TO KNOWN INITIAL STATE FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 6 285 00B1' M_INIT: 286 00B1' 3E 80 LD A,NULL 287 00B3' 32 0000' LD (C_DATA),A ; fool it into hanging up 288 00B6' 3E CC LD A,DEFAULT ; desired default value 289 290 ; ************************* 291 ; SET_UART 292 ; SETS UART TO DESIRED STOP BITS, PARITY, ETC 293 ; ENTRY: A=stop bits + bits/char + parity 294 ; EXIT: NONE 295 00B8' SET_UART: 296 00B8' F6 03 OR X64 ; clock rate is always 64x 297 00BA' F5 PUSH AF 298 00BB' 3E 80 LD A,080H 299 00BD' D3 5F OUT (CTRLP),A 300 00BF' D3 5F OUT (CTRLP),A ; get the 8251's attention 301 00C1' 3E 40 LD A,040H 302 00C3' D3 5F OUT (CTRLP),A 303 00C5' F1 POP AF 304 00C6' D3 5F OUT (CTRLP),A ; dump the init value out 305 00C8' 3A 0000' LD A,(C_DATA) 306 00CB' D3 5F OUT (CTRLP),A 307 00CD' C9 RET 0 Error(s) Detected. 206 Program Bytes. 54 Symbols Detected. FILE: MODDOC:MODEM HEWLETT-PACKARD: Z80 Assembler Tue, 9 Oct 1984, 11:26 Page 7 Value Symbol Defined Referenced: 006D' ANSMOD 202 86 005A' BAD_DGT 175 131 133 0006 BD 77 0000 BITS5 27 0004 BITS6 28 0008 BITS7 29 000C BITS8 30 39 0007 CD 79 0081' CD_STAT 225 87 0031' CHAR_OK 137 134 0098' CHR_ERR 259 008F' CHR_IN 253 88 255 00A7' CHR_L1 274 277 00A6' CHR_OUT 271 88 005F CTRLP 11 147 156 193 205 208 217 226 238 262 264 275 299 300 302 304 306 0000' C_DATA 82 167 192 207 216 260 287 305 005E DATAP 10 256 280 00CC DEFAULT 39 288 0001' DELAY 96 86 151 160 173 0015' DIAL 118 86 0007 DSR 78 79 227 0002 DTR 52 155 191 204 206 0080 EHM 44 0020 EP 32 0010 ER 48 261 263 0005 FE 76 0079' HANGUP 214 87 190 0040 IR 46 00B1' M_INIT 285 88 0080 NULL 14 82 286 0004 OE 75 0053' PAUSE 170 125 127 129 0010 PEN 33 003B' PLP1 150 152 0048' PLP2 159 161 0055' PLP3 172 174 0034' PLSE_LP 141 165 0003 P_ERR 74 0020 RTS 47 146 155 191 206 215 0004 RXE 50 146 155 191 204 206 215 0001 RXRDY 72 244 0008 SBRK 49 005F' SEIZE 188 86 00B8' SET_UART 295 89 0040 STPB1 23 0080 STPB15 24 00C0 STPB2 25 39 0001 TXE 51 146 155 191 204 206 215 0002 TXMT 73 276 0000 TXRDY 71 008C' URT_CMN 243 240 008B' URT_ERR 241 0086' U_STAT 237 87 254 0003 X64 36 296